1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26 import java.io.BufferedReader;
27 import java.io.ByteArrayInputStream;
28 import java.io.ByteArrayOutputStream;
29 import java.io.File;
30 import java.io.FileInputStream;
31 import java.io.InputStreamReader;
32 import java.io.ObjectInputStream;
33 import java.io.ObjectOutputStream;
34 import java.net.URISyntaxException;
35 import java.net.URL;
36 import java.text.DecimalFormatSymbols;
37 import java.util.ArrayList;
38 import java.util.Arrays;
39 import java.util.Calendar;
40 import java.util.IllformedLocaleException;
41 import java.util.List;
42 import java.util.Locale;
43 import java.util.Locale.Builder;
44 import java.util.Set;
45
46
47
48
49
50
51
52
53 public class LocaleEnhanceTest extends LocaleTestFmwk {
54
55 public static void main(String[] args) throws Exception {
56 List<String> argList = new ArrayList<String>();
57 argList.addAll(Arrays.asList(args));
58 argList.add("-nothrow");
59 new LocaleEnhanceTest().run(argList.toArray(new String[argList.size()]));
60 }
61
62 public LocaleEnhanceTest() {
63 }
64
65
66
67
68
69
70 private static final String l = "en";
71
72
73 private static final String s = "Latn";
74
75
76 private static final String c = "US";
77
78
79 private static final String v = "NewYork";
80
81
82
83
84
85 public void testCreateLocaleCanonicalValid() {
86 String[] valids = {
87 "en-Latn-US-NewYork", "en_US_NewYork_#Latn",
88 "en-Latn-US", "en_US_#Latn",
89 "en-Latn-NewYork", "en__NewYork_#Latn",
90 "en-Latn", "en__#Latn",
91 "en-US-NewYork", "en_US_NewYork",
92 "en-US", "en_US",
93 "en-NewYork", "en__NewYork",
94 "en", "en",
95 "und-Latn-US-NewYork", "_US_NewYork_#Latn",
96 "und-Latn-US", "_US_#Latn",
97 "und-Latn-NewYork", "",
98 "und-Latn", "",
99 "und-US-NewYork", "_US_NewYork",
100 "und-US", "_US",
101 "und-NewYork", "",
102 "und", ""
103 };
104
105 Builder builder = new Builder();
106
107 for (int i = 0; i < valids.length; i += 2) {
108 String tag = valids[i];
109 String id = valids[i+1];
110
111 String idl = (i & 16) == 0 ? l : "";
112 String ids = (i & 8) == 0 ? s : "";
113 String idc = (i & 4) == 0 ? c : "";
114 String idv = (i & 2) == 0 ? v : "";
115
116 String msg = String.valueOf(i/2) + ": '" + tag + "' ";
117
118 try {
119 Locale l = builder
120 .setLanguage(idl)
121 .setScript(ids)
122 .setRegion(idc)
123 .setVariant(idv)
124 .build();
125 assertEquals(msg + "language", idl, l.getLanguage());
126 assertEquals(msg + "script", ids, l.getScript());
127 assertEquals(msg + "country", idc, l.getCountry());
128 assertEquals(msg + "variant", idv, l.getVariant());
129 assertEquals(msg + "tag", tag, l.toLanguageTag());
130 assertEquals(msg + "id", id, l.toString());
131 }
132 catch (IllegalArgumentException e) {
133 errln(msg + e.getMessage());
134 }
135 }
136 }
137
138
139
140
141
142
143
144
145
146
147
148 public void testCreateLocaleMultipleVariants() {
149
150 String[] valids = {
151 "en-Latn-US-Newer-Yorker", "en_US_Newer_Yorker_#Latn",
152 "en-Latn-Newer-Yorker", "en__Newer_Yorker_#Latn",
153 "en-US-Newer-Yorker", "en_US_Newer_Yorker",
154 "en-Newer-Yorker", "en__Newer_Yorker",
155 "und-Latn-US-Newer-Yorker", "_US_Newer_Yorker_#Latn",
156 "und-Latn-Newer-Yorker", "",
157 "und-US-Newer-Yorker", "_US_Newer_Yorker",
158 "und-Newer-Yorker", "",
159 };
160
161 Builder builder = new Builder();
162
163 final String idv = "Newer_Yorker";
164 for (int i = 0; i < valids.length; i += 2) {
165 String tag = valids[i];
166 String id = valids[i+1];
167
168 String idl = (i & 8) == 0 ? l : "";
169 String ids = (i & 4) == 0 ? s : "";
170 String idc = (i & 2) == 0 ? c : "";
171
172 String msg = String.valueOf(i/2) + ": " + tag + " ";
173 try {
174 Locale l = builder
175 .setLanguage(idl)
176 .setScript(ids)
177 .setRegion(idc)
178 .setVariant(idv)
179 .build();
180
181 assertEquals(msg + " language", idl, l.getLanguage());
182 assertEquals(msg + " script", ids, l.getScript());
183 assertEquals(msg + " country", idc, l.getCountry());
184 assertEquals(msg + " variant", idv, l.getVariant());
185
186 assertEquals(msg + "tag", tag, l.toLanguageTag());
187 assertEquals(msg + "id", id, l.toString());
188 }
189 catch (IllegalArgumentException e) {
190 errln(msg + e.getMessage());
191 }
192 }
193 }
194
195
196
197
198
199 public void testCreateLocaleCanonicalInvalidSeparator() {
200 String[] invalids = {
201
202 "en_Latn_US_NewYork_",
203 "en_Latn_US_",
204 "en_Latn_",
205 "en_",
206 "_",
207
208
209 "en_Latn_US__NewYork",
210 "_Latn_US__NewYork",
211 "en_US__NewYork",
212 "_US__NewYork",
213
214
215
216
217
218
219
220
221 "__US",
222 "__NewYork",
223
224
225 "en___NewYork",
226 "en_Latn___NewYork",
227 "_Latn___NewYork",
228 "___NewYork",
229 };
230
231 for (int i = 0; i < invalids.length; ++i) {
232 String id = invalids[i];
233 Locale l = Locale.forLanguageTag(id);
234 assertEquals(id, "und", l.toLanguageTag());
235 }
236 }
237
238
239
240
241
242 public void testCurrentLocales() {
243 Locale[] locales = java.text.DateFormat.getAvailableLocales();
244 Builder builder = new Builder();
245
246 for (Locale target : locales) {
247 String tag = target.toLanguageTag();
248
249
250
251 Locale tagResult = Locale.forLanguageTag(tag);
252 if (!target.getVariant().equals("NY")) {
253 assertEquals("tagResult", target, tagResult);
254 }
255
256
257
258 Locale builderResult = builder.setLocale(target).build();
259 if (target.getVariant().length() != 2) {
260 assertEquals("builderResult", target, builderResult);
261 }
262 }
263 }
264
265
266
267
268 public void testIcuLocales() throws Exception {
269 BufferedReader br = new BufferedReader(
270 new InputStreamReader(
271 LocaleEnhanceTest.class.getResourceAsStream("icuLocales.txt"),
272 "UTF-8"));
273 String id = null;
274 while (null != (id = br.readLine())) {
275 Locale result = Locale.forLanguageTag(id);
276 assertEquals("ulocale", id, result.toLanguageTag());
277 }
278 }
279
280
281
282
283
284 public void testConstructor() {
285
286 String[][] tests = {
287
288
289 { "X", "y", "z", "x", "Y" },
290
291 { "xXxXxXxXxXxX", "yYyYyYyYyYyYyYyY", "zZzZzZzZzZzZzZzZ",
292 "xxxxxxxxxxxx", "YYYYYYYYYYYYYYYY" },
293
294 { "he", "IW", "", "iw" },
295 { "iw", "IW", "", "iw" },
296 { "yi", "DE", "", "ji" },
297 { "ji", "DE", "", "ji" },
298 { "id", "ID", "", "in" },
299 { "in", "ID", "", "in" },
300
301 { "ja", "JP", "JP" },
302 { "th", "TH", "TH" },
303 { "no", "NO", "NY" },
304 { "no", "NO", "NY" },
305
306 { "eng", "US", "" }
307 };
308 for (int i = 0; i < tests.length; ++ i) {
309 String[] test = tests[i];
310 String id = String.valueOf(i);
311 Locale locale = new Locale(test[0], test[1], test[2]);
312 assertEquals(id + " lang", test.length > 3 ? test[3] : test[0], locale.getLanguage());
313 assertEquals(id + " region", test.length > 4 ? test[4] : test[1], locale.getCountry());
314 assertEquals(id + " variant", test.length > 5 ? test[5] : test[2], locale.getVariant());
315 }
316 }
317
318
319
320
321
322 public void testGetScript() {
323
324 Locale locale = Locale.forLanguageTag("und-latn");
325 assertEquals("forLanguageTag", "Latn", locale.getScript());
326
327
328 locale = new Builder().setScript("LATN").build();
329 assertEquals("builder", "Latn", locale.getScript());
330
331
332 locale = Locale.forLanguageTag("und");
333 assertEquals("script is empty string", "", locale.getScript());
334 }
335
336 public void testGetExtension() {
337
338 Locale locale = Locale.forLanguageTag("und-a-some_ex-tension");
339 assertEquals("some_ex-tension", null, locale.getExtension('a'));
340
341
342 locale = new Builder().setExtension('a', "some-ex-tension").build();
343 assertEquals("builder", "some-ex-tension", locale.getExtension('a'));
344
345
346 assertEquals("empty b", null, locale.getExtension('b'));
347
348
349 new ExpectIAE() { public void call() { Locale.forLanguageTag("").getExtension('\uD800'); }};
350
351
352 locale = Locale.forLanguageTag("x-y-z-blork");
353 assertEquals("x", "y-z-blork", locale.getExtension('x'));
354 }
355
356 public void testGetExtensionKeys() {
357 Locale locale = Locale.forLanguageTag("und-a-xx-yy-b-zz-ww");
358 Set<Character> result = locale.getExtensionKeys();
359 assertEquals("result size", 2, result.size());
360 assertTrue("'a','b'", result.contains('a') && result.contains('b'));
361
362
363 try {
364 result.add('x');
365 errln("expected exception on add to extension key set");
366 }
367 catch (UnsupportedOperationException e) {
368
369 }
370
371
372 locale = Locale.forLanguageTag("und");
373 assertTrue("empty result", locale.getExtensionKeys().isEmpty());
374 }
375
376 public void testGetUnicodeLocaleAttributes() {
377 Locale locale = Locale.forLanguageTag("en-US-u-abc-def");
378 Set<String> attributes = locale.getUnicodeLocaleAttributes();
379 assertEquals("number of attributes", 2, attributes.size());
380 assertTrue("attribute abc", attributes.contains("abc"));
381 assertTrue("attribute def", attributes.contains("def"));
382
383 locale = Locale.forLanguageTag("en-US-u-ca-gregory");
384 attributes = locale.getUnicodeLocaleAttributes();
385 assertTrue("empty attributes", attributes.isEmpty());
386 }
387
388 public void testGetUnicodeLocaleType() {
389 Locale locale = Locale.forLanguageTag("und-u-co-japanese-nu-thai");
390 assertEquals("collation", "japanese", locale.getUnicodeLocaleType("co"));
391 assertEquals("numbers", "thai", locale.getUnicodeLocaleType("nu"));
392
393
394 assertEquals("key case", "japanese", locale.getUnicodeLocaleType("Co"));
395
396
397 assertEquals("locale keyword not present", null, locale.getUnicodeLocaleType("xx"));
398
399
400 locale = Locale.forLanguageTag("und");
401 assertEquals("locale extension not present", null, locale.getUnicodeLocaleType("co"));
402
403
404 locale = Locale.forLanguageTag("und-u-kn");
405 assertEquals("typeless keyword", "", locale.getUnicodeLocaleType("kn"));
406
407
408 new ExpectIAE() { public void call() { Locale.forLanguageTag("").getUnicodeLocaleType("q"); }};
409 new ExpectIAE() { public void call() { Locale.forLanguageTag("").getUnicodeLocaleType("abcdefghi"); }};
410
411
412 new ExpectNPE() { public void call() { Locale.forLanguageTag("").getUnicodeLocaleType(null); }};
413 }
414
415 public void testGetUnicodeLocaleKeys() {
416 Locale locale = Locale.forLanguageTag("und-u-co-japanese-nu-thai");
417 Set<String> result = locale.getUnicodeLocaleKeys();
418 assertEquals("two keys", 2, result.size());
419 assertTrue("co and nu", result.contains("co") && result.contains("nu"));
420
421
422 try {
423 result.add("frobozz");
424 errln("expected exception when add to locale key set");
425 }
426 catch (UnsupportedOperationException e) {
427
428 }
429 }
430
431 public void testPrivateUseExtension() {
432 Locale locale = Locale.forLanguageTag("x-y-x-blork-");
433 assertEquals("blork", "y-x-blork", locale.getExtension(Locale.PRIVATE_USE_EXTENSION));
434
435 locale = Locale.forLanguageTag("und");
436 assertEquals("no privateuse", null, locale.getExtension(Locale.PRIVATE_USE_EXTENSION));
437 }
438
439 public void testToLanguageTag() {
440
441
442 String[][] tests = {
443
444 { "", "", "", "und" },
445
446 { "", "", "NewYork", "und-NewYork" },
447
448 { "", "Us", "", "und-US" },
449 { "", "US", "NewYork", "und-US-NewYork" },
450 { "EN", "", "", "en" },
451 { "EN", "", "NewYork", "en-NewYork" },
452 { "EN", "US", "", "en-US" },
453 { "EN", "US", "NewYork", "en-US-NewYork" },
454
455 { "en", "US", "Newer_Yorker", "en-US-Newer-Yorker" },
456
457 { "en", "US", "new_yorker", "en-US-x-lvariant-new-yorker" },
458
459 { "en", "US", "Windows_XP_Home", "en-US-Windows-x-lvariant-XP-Home" },
460
461 { "en", "US", "WindowsVista_SP2", "en-US" },
462
463 { "en", "USA", "", "en" },
464
465 { "e", "US", "", "und-US" },
466
467 { "Eng", "", "", "eng" },
468
469 { "he", "IW", "", "he-IW" },
470 { "iw", "IW", "", "he-IW" },
471 { "yi", "DE", "", "yi-DE" },
472 { "ji", "DE", "", "yi-DE" },
473 { "id", "ID", "", "id-ID" },
474 { "in", "ID", "", "id-ID" },
475
476 { "ja", "JP", "JP", "ja-JP-u-ca-japanese-x-lvariant-JP" },
477 { "th", "TH", "TH", "th-TH-u-nu-thai-x-lvariant-TH" },
478 { "no", "NO", "NY", "nn-NO" }
479 };
480 for (int i = 0; i < tests.length; ++i) {
481 String[] test = tests[i];
482 Locale locale = new Locale(test[0], test[1], test[2]);
483 assertEquals("case " + i, test[3], locale.toLanguageTag());
484 }
485
486
487 String[][] tests1 = {
488
489 { "EN-us", "en-US" },
490 { "en-Latn-US", "en-Latn-US" },
491
492 { "de-u-co-phonebk-ca-gregory", "de-u-ca-gregory-co-phonebk" },
493
494 { "x-elmer", "x-elmer" },
495 { "x-lvariant-JP", "x-lvariant-JP" },
496 };
497 for (String[] test : tests1) {
498 Locale locale = Locale.forLanguageTag(test[0]);
499 assertEquals("case " + test[0], test[1], locale.toLanguageTag());
500 }
501
502 }
503
504 public void testForLanguageTag() {
505
506
507
508
509
510 String[][] tests = {
511
512 { "x-abc", "x-abc" },
513 { "x-a-b-c", "x-a-b-c" },
514 { "x-a-12345678", "x-a-12345678" },
515
516
517 { "i-ami", "ami" },
518 { "i-bnn", "bnn" },
519 { "i-hak", "hak" },
520 { "i-klingon", "tlh" },
521 { "i-lux", "lb" },
522 { "i-navajo", "nv" },
523 { "i-pwn", "pwn" },
524 { "i-tao", "tao" },
525 { "i-tay", "tay" },
526 { "i-tsu", "tsu" },
527 { "art-lojban", "jbo" },
528 { "no-bok", "nb" },
529 { "no-nyn", "nn" },
530 { "sgn-BE-FR", "sfb" },
531 { "sgn-BE-NL", "vgt" },
532 { "sgn-CH-DE", "sgg" },
533 { "zh-guoyu", "cmn" },
534 { "zh-hakka", "hak" },
535 { "zh-min-nan", "nan" },
536 { "zh-xiang", "hsn" },
537
538
539
540 { "i-default", "en-x-i-default" },
541 { "i-enochian", "x-i-enochian" },
542 { "i-mingo", "see-x-i-mingo" },
543 { "en-GB-oed", "en-GB-x-oed" },
544 { "zh-min", "nan-x-zh-min" },
545 { "cel-gaulish", "xtg-x-cel-gaulish" },
546 };
547 for (int i = 0; i < tests.length; ++i) {
548 String[] test = tests[i];
549 Locale locale = Locale.forLanguageTag(test[0]);
550 assertEquals("grandfathered case " + i, test[1], locale.toLanguageTag());
551 }
552
553
554
555 tests = new String[][] {
556 { "valid",
557 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-x-y-12345678-z",
558 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-x-y-12345678-z" },
559 { "segment of private use tag too long",
560 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-x-y-123456789-z",
561 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-x-y" },
562 { "segment of private use tag is empty",
563 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-x-y--12345678-z",
564 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-x-y" },
565 { "first segment of private use tag is empty",
566 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-x--y-12345678-z",
567 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def" },
568 { "illegal extension tag",
569 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def-\uD800-y-12345678-z",
570 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-def" },
571 { "locale subtag with no value",
572 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-x-y-12345678-z",
573 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-bb-x-y-12345678-z" },
574 { "locale key subtag invalid",
575 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc-123456789-def-x-y-12345678-z",
576 "en-US-Newer-Yorker-a-bb-cc-dd-u-aa-abc" },
577
578
579 { "locale key subtag invalid in earlier position",
580 "en-US-Newer-Yorker-a-bb-cc-dd-u-123456789-abc-bb-def-x-y-12345678-z",
581 "en-US-Newer-Yorker-a-bb-cc-dd" },
582 };
583 for (int i = 0; i < tests.length; ++i) {
584 String[] test = tests[i];
585 String msg = "syntax error case " + i + " " + test[0];
586 try {
587 Locale locale = Locale.forLanguageTag(test[1]);
588 assertEquals(msg, test[2], locale.toLanguageTag());
589 }
590 catch (IllegalArgumentException e) {
591 errln(msg + " caught exception: " + e);
592 }
593 }
594
595
596 Locale locale = Locale.forLanguageTag("und-d-aa-00-bb-01-D-AA-10-cc-11-c-1234");
597 assertEquals("extension", "aa-00-bb-01", locale.getExtension('d'));
598 assertEquals("extension c", "1234", locale.getExtension('c'));
599
600 locale = Locale.forLanguageTag("und-U-ca-gregory-u-ca-japanese");
601 assertEquals("Unicode extension", "ca-gregory", locale.getExtension(Locale.UNICODE_LOCALE_EXTENSION));
602
603
604 locale = Locale.forLanguageTag("und-u-aa-000-bb-001-bB-002-cc-003-c-1234");
605 assertEquals("Unicode keywords", "aa-000-bb-001-cc-003", locale.getExtension(Locale.UNICODE_LOCALE_EXTENSION));
606 assertEquals("Duplicated Unicode locake key followed by an extension", "1234", locale.getExtension('c'));
607 }
608
609 public void testGetDisplayScript() {
610 Locale latnLocale = Locale.forLanguageTag("und-latn");
611 Locale hansLocale = Locale.forLanguageTag("und-hans");
612
613 Locale oldLocale = Locale.getDefault();
614
615 Locale.setDefault(Locale.US);
616 assertEquals("latn US", "Latin", latnLocale.getDisplayScript());
617 assertEquals("hans US", "Simplified Han", hansLocale.getDisplayScript());
618
619 Locale.setDefault(Locale.GERMANY);
620 assertEquals("latn DE", "Lateinisch", latnLocale.getDisplayScript());
621 assertEquals("hans DE", "Vereinfachte Chinesische Schrift", hansLocale.getDisplayScript());
622
623 Locale.setDefault(oldLocale);
624 }
625
626 public void testGetDisplayScriptWithLocale() {
627 Locale latnLocale = Locale.forLanguageTag("und-latn");
628 Locale hansLocale = Locale.forLanguageTag("und-hans");
629
630 assertEquals("latn US", "Latin", latnLocale.getDisplayScript(Locale.US));
631 assertEquals("hans US", "Simplified Han", hansLocale.getDisplayScript(Locale.US));
632
633 assertEquals("latn DE", "Lateinisch", latnLocale.getDisplayScript(Locale.GERMANY));
634 assertEquals("hans DE", "Vereinfachte Chinesische Schrift", hansLocale.getDisplayScript(Locale.GERMANY));
635 }
636
637 public void testGetDisplayName() {
638 final Locale[] testLocales = {
639 Locale.ROOT,
640 new Locale("en"),
641 new Locale("en", "US"),
642 new Locale("", "US"),
643 new Locale("no", "NO", "NY"),
644 new Locale("", "", "NY"),
645 Locale.forLanguageTag("zh-Hans"),
646 Locale.forLanguageTag("zh-Hant"),
647 Locale.forLanguageTag("zh-Hans-CN"),
648 Locale.forLanguageTag("und-Hans"),
649 };
650
651 final String[] displayNameEnglish = {
652 "",
653 "English",
654 "English (United States)",
655 "United States",
656 "Norwegian (Norway,Nynorsk)",
657 "Nynorsk",
658 "Chinese (Simplified Han)",
659 "Chinese (Traditional Han)",
660 "Chinese (Simplified Han,China)",
661 "Simplified Han",
662 };
663
664 final String[] displayNameSimplifiedChinese = {
665 "",
666 "\u82f1\u6587",
667 "\u82f1\u6587 (\u7f8e\u56fd)",
668 "\u7f8e\u56fd",
669 "\u632a\u5a01\u6587 (\u632a\u5a01,Nynorsk)",
670 "Nynorsk",
671 "\u4e2d\u6587 (\u7b80\u4f53\u4e2d\u6587)",
672 "\u4e2d\u6587 (\u7e41\u4f53\u4e2d\u6587)",
673 "\u4e2d\u6587 (\u7b80\u4f53\u4e2d\u6587,\u4e2d\u56fd)",
674 "\u7b80\u4f53\u4e2d\u6587",
675 };
676
677 for (int i = 0; i < testLocales.length; i++) {
678 Locale loc = testLocales[i];
679 assertEquals("English display name for " + loc.toLanguageTag(),
680 displayNameEnglish[i], loc.getDisplayName(Locale.ENGLISH));
681 assertEquals("Simplified Chinese display name for " + loc.toLanguageTag(),
682 displayNameSimplifiedChinese[i], loc.getDisplayName(Locale.CHINA));
683 }
684 }
685
686
687
688
689
690 public void testBuilderSetLocale() {
691 Builder builder = new Builder();
692 Builder lenientBuilder = new Builder();
693
694 String languageTag = "en-Latn-US-NewYork-a-bb-ccc-u-co-japanese-x-y-z";
695 String target = "en-Latn-US-NewYork-a-bb-ccc-u-co-japanese-x-y-z";
696
697 Locale locale = Locale.forLanguageTag(languageTag);
698 Locale result = lenientBuilder
699 .setLocale(locale)
700 .build();
701 assertEquals("long tag", target, result.toLanguageTag());
702 assertEquals("long tag", locale, result);
703
704
705 new BuilderNPE("locale") {
706 public void call() { b.setLocale(null); }
707 };
708
709
710
711 locale = builder.setLocale(new Locale("ja", "JP", "JP")).build();
712 assertEquals("ja_JP_JP languagetag", "ja-JP-u-ca-japanese", locale.toLanguageTag());
713 assertEquals("ja_JP_JP variant", "", locale.getVariant());
714
715 locale = builder.setLocale(new Locale("th", "TH", "TH")).build();
716 assertEquals("th_TH_TH languagetag", "th-TH-u-nu-thai", locale.toLanguageTag());
717 assertEquals("th_TH_TH variant", "", locale.getVariant());
718
719 locale = builder.setLocale(new Locale("no", "NO", "NY")).build();
720 assertEquals("no_NO_NY languagetag", "nn-NO", locale.toLanguageTag());
721 assertEquals("no_NO_NY language", "nn", locale.getLanguage());
722 assertEquals("no_NO_NY variant", "", locale.getVariant());
723
724
725 new BuilderILE("123_4567_89") {
726 public void call() {
727 b.setLocale(new Locale("123", "4567", "89"));
728 }
729 };
730 }
731
732 public void testBuilderSetLanguageTag() {
733 String source = "eN-LaTn-Us-NewYork-A-Xx-B-Yy-X-1-2-3";
734 String target = "en-Latn-US-NewYork-a-xx-b-yy-x-1-2-3";
735 Builder builder = new Builder();
736 String result = builder
737 .setLanguageTag(source)
738 .build()
739 .toLanguageTag();
740 assertEquals("language", target, result);
741
742
743 new BuilderILE() { public void call() { b.setLanguageTag("und-a-xx-yy-b-ww-A-00-11-c-vv"); }};
744
745
746 new BuilderILE() { public void call() { b.setLanguageTag("und-u-nu-thai-NU-chinese-xx-1234"); }};
747 }
748
749 public void testBuilderSetLanguage() {
750
751 String source = "eN";
752 String target = "en";
753 String defaulted = "";
754 Builder builder = new Builder();
755 String result = builder
756 .setLanguage(source)
757 .build()
758 .getLanguage();
759 assertEquals("en", target, result);
760
761
762 result = builder
763 .setLanguage(target)
764 .setLanguage("")
765 .build()
766 .getLanguage();
767 assertEquals("empty", defaulted, result);
768
769
770 result = builder
771 .setLanguage(target)
772 .setLanguage(null)
773 .build()
774 .getLanguage();
775 assertEquals("null", defaulted, result);
776
777
778
779
780 new BuilderILE("q", "abcdefghi", "13") { public void call() { b.setLanguage(arg); }};
781
782
783 assertNotNull("2alpha", builder.setLanguage("zz").build());
784 assertNotNull("8alpha", builder.setLanguage("abcdefgh").build());
785
786
787 result = builder
788 .setLanguage("eng")
789 .build()
790 .getLanguage();
791 assertEquals("eng", "eng", result);
792 }
793
794 public void testBuilderSetScript() {
795
796 String source = "lAtN";
797 String target = "Latn";
798 String defaulted = "";
799 Builder builder = new Builder();
800 String result = builder
801 .setScript(source)
802 .build()
803 .getScript();
804 assertEquals("script", target, result);
805
806
807 result = builder
808 .setScript(target)
809 .setScript("")
810 .build()
811 .getScript();
812 assertEquals("empty", defaulted, result);
813
814
815 result = builder
816 .setScript(target)
817 .setScript(null)
818 .build()
819 .getScript();
820 assertEquals("null", defaulted, result);
821
822
823
824 new BuilderILE("abc", "abcde", "l3tn") { public void call() { b.setScript(arg); }};
825
826
827 assertEquals("4alpha", "Wxyz", builder.setScript("wxyz").build().getScript());
828 }
829
830 public void testBuilderSetRegion() {
831
832 String source = "uS";
833 String target = "US";
834 String defaulted = "";
835 Builder builder = new Builder();
836 String result = builder
837 .setRegion(source)
838 .build()
839 .getCountry();
840 assertEquals("us", target, result);
841
842
843 result = builder
844 .setRegion(target)
845 .setRegion("")
846 .build()
847 .getCountry();
848 assertEquals("empty", defaulted, result);
849
850
851 result = builder
852 .setRegion(target)
853 .setRegion(null)
854 .build()
855 .getCountry();
856 assertEquals("null", defaulted, result);
857
858
859
860 new BuilderILE("q", "abc", "12", "1234", "a3", "12a") { public void call() { b.setRegion(arg); }};
861
862
863 assertEquals("2alpha", "ZZ", builder.setRegion("ZZ").build().getCountry());
864 assertEquals("3digit", "000", builder.setRegion("000").build().getCountry());
865 }
866
867 public void testBuilderSetVariant() {
868
869 String source = "NewYork";
870 String target = source;
871 String defaulted = "";
872 Builder builder = new Builder();
873 String result = builder
874 .setVariant(source)
875 .build()
876 .getVariant();
877 assertEquals("NewYork", target, result);
878
879 result = builder
880 .setVariant("NeWeR_YoRkEr")
881 .build()
882 .toLanguageTag();
883 assertEquals("newer yorker", "und-NeWeR-YoRkEr", result);
884
885
886 result = builder
887 .setVariant("zzzzz_yyyyy_xxxxx")
888 .build()
889 .getVariant();
890 assertEquals("zyx", "zzzzz_yyyyy_xxxxx", result);
891
892
893 result = builder
894 .setVariant(target)
895 .setVariant("")
896 .build()
897 .getVariant();
898 assertEquals("empty", defaulted, result);
899
900
901 result = builder
902 .setVariant(target)
903 .setVariant(null)
904 .build()
905 .getVariant();
906 assertEquals("null", defaulted, result);
907
908
909
910 new BuilderILE("abcd", "abcdefghi", "1ab", "1abcdefgh") { public void call() { b.setVariant(arg); }};
911
912
913 assertEquals("digit+3alpha", "1abc", builder.setVariant("1abc").build().getVariant());
914
915
916 new BuilderILE("abcde-fg") { public void call() { b.setVariant(arg); }};
917 }
918
919 public void testBuilderSetExtension() {
920
921 final char sourceKey = 'a';
922 final String sourceValue = "aB-aBcdefgh-12-12345678";
923 String target = "ab-abcdefgh-12-12345678";
924 Builder builder = new Builder();
925 String result = builder
926 .setExtension(sourceKey, sourceValue)
927 .build()
928 .getExtension(sourceKey);
929 assertEquals("extension", target, result);
930
931
932 result = builder
933 .setExtension(sourceKey, sourceValue)
934 .setExtension(sourceKey, "")
935 .build()
936 .getExtension(sourceKey);
937 assertEquals("empty", null, result);
938
939
940 result = builder
941 .setExtension(sourceKey, sourceValue)
942 .setExtension(sourceKey, null)
943 .build()
944 .getExtension(sourceKey);
945 assertEquals("null", null, result);
946
947
948
949 new BuilderILE("$") { public void call() { b.setExtension('$', sourceValue); }};
950
951
952 new BuilderILE("ab-cd-123456789") { public void call() { b.setExtension(sourceKey, arg); }};
953
954
955 new BuilderILE("ab--cd") { public void call() { b.setExtension(sourceKey, arg); }};
956
957
958 Locale locale = builder
959 .setExtension('u', "co-japanese")
960 .build();
961 assertEquals("locale extension", "japanese", locale.getUnicodeLocaleType("co"));
962
963
964 Locale locale2 = builder
965 .setUnicodeLocaleKeyword("co", "japanese")
966 .build();
967 assertEquals("locales with extension", locale, locale2);
968
969
970 Locale locale3 = builder
971 .setExtension('u', "xxx-nu-thai")
972 .build();
973 assertEquals("remove co", null, locale3.getUnicodeLocaleType("co"));
974 assertEquals("override thai", "thai", locale3.getUnicodeLocaleType("nu"));
975 assertEquals("override attribute", 1, locale3.getUnicodeLocaleAttributes().size());
976
977
978 Locale locale4 = builder
979 .setUnicodeLocaleKeyword("co", "japanese")
980 .build();
981 assertEquals("extend", "japanese", locale4.getUnicodeLocaleType("co"));
982 assertEquals("extend", "thai", locale4.getUnicodeLocaleType("nu"));
983
984
985 result = builder
986 .clear()
987 .setExtension('u', "456-123-zz-123-yy-456-xx-789")
988 .build()
989 .toLanguageTag();
990 assertEquals("reorder", "und-u-123-456-xx-789-yy-456-zz-123", result);
991
992
993 result = builder
994 .clear()
995 .setExtension('u', "nu-thai-foobar")
996 .build()
997 .getUnicodeLocaleType("nu");
998 assertEquals("multiple types", "thai-foobar", result);
999
1000
1001 result = builder
1002 .clear()
1003 .setExtension('u', "nu-thai-NU-chinese-xx-1234")
1004 .build()
1005 .toLanguageTag();
1006 assertEquals("duplicate keys", "und-u-nu-thai-xx-1234", result);
1007 }
1008
1009 public void testBuilderAddUnicodeLocaleAttribute() {
1010 Builder builder = new Builder();
1011 Locale locale = builder
1012 .addUnicodeLocaleAttribute("def")
1013 .addUnicodeLocaleAttribute("abc")
1014 .build();
1015
1016 Set<String> uattrs = locale.getUnicodeLocaleAttributes();
1017 assertEquals("number of attributes", 2, uattrs.size());
1018 assertTrue("attribute abc", uattrs.contains("abc"));
1019 assertTrue("attribute def", uattrs.contains("def"));
1020
1021
1022 locale = builder.removeUnicodeLocaleAttribute("xxx")
1023 .build();
1024
1025 assertEquals("remove bogus", 2, uattrs.size());
1026
1027
1028 locale = builder.addUnicodeLocaleAttribute("abc")
1029 .build();
1030 assertEquals("add duplicate", 2, uattrs.size());
1031
1032
1033 new BuilderNPE("null attribute") { public void call() { b.addUnicodeLocaleAttribute(null); }};
1034
1035
1036 new BuilderILE("invalid attribute") { public void call() { b.addUnicodeLocaleAttribute("ca"); }};
1037 }
1038
1039 public void testBuildersetUnicodeLocaleKeyword() {
1040
1041 Builder builder = new Builder();
1042 Locale locale = builder
1043 .setUnicodeLocaleKeyword("co", "japanese")
1044 .setUnicodeLocaleKeyword("nu", "thai")
1045 .build();
1046 assertEquals("co", "japanese", locale.getUnicodeLocaleType("co"));
1047 assertEquals("nu", "thai", locale.getUnicodeLocaleType("nu"));
1048 assertEquals("keys", 2, locale.getUnicodeLocaleKeys().size());
1049
1050
1051 String result = builder
1052 .setUnicodeLocaleKeyword("co", null)
1053 .build()
1054 .toLanguageTag();
1055 assertEquals("empty co", "und-u-nu-thai", result);
1056
1057
1058 result = builder
1059 .setUnicodeLocaleKeyword("nu", null)
1060 .build()
1061 .toLanguageTag();
1062 assertEquals("empty nu", "und", result);
1063
1064
1065 result = builder
1066 .setUnicodeLocaleKeyword("zz", "012")
1067 .setUnicodeLocaleKeyword("aa", "345")
1068 .build()
1069 .toLanguageTag();
1070 assertEquals("reordered", "und-u-aa-345-zz-012", result);
1071
1072
1073 new BuilderNPE("keyword") { public void call() { b.setUnicodeLocaleKeyword(null, "thai"); }};
1074
1075
1076 new BuilderILE("a", "abc") { public void call() { b.setUnicodeLocaleKeyword(arg, "value"); }};
1077
1078
1079 new BuilderILE("ab", "abcdefghi") { public void call() { b.setUnicodeLocaleKeyword("ab", arg); }};
1080 }
1081
1082 public void testBuilderPrivateUseExtension() {
1083
1084 String source = "c-B-a";
1085 String target = "c-b-a";
1086 Builder builder = new Builder();
1087 String result = builder
1088 .setExtension(Locale.PRIVATE_USE_EXTENSION, source)
1089 .build()
1090 .getExtension(Locale.PRIVATE_USE_EXTENSION);
1091 assertEquals("abc", target, result);
1092
1093
1094 new BuilderILE("a--b") { public void call() { b.setExtension(Locale.PRIVATE_USE_EXTENSION, arg); }};
1095 }
1096
1097 public void testBuilderClear() {
1098 String monster = "en-latn-US-NewYork-a-bb-cc-u-co-japanese-x-z-y-x-x";
1099 Builder builder = new Builder();
1100 Locale locale = Locale.forLanguageTag(monster);
1101 String result = builder
1102 .setLocale(locale)
1103 .clear()
1104 .build()
1105 .toLanguageTag();
1106 assertEquals("clear", "und", result);
1107 }
1108
1109 public void testBuilderRemoveUnicodeAttribute() {
1110
1111 }
1112
1113 public void testBuilderBuild() {
1114
1115 }
1116
1117 public void testSerialize() {
1118 final Locale[] testLocales = {
1119 Locale.ROOT,
1120 new Locale("en"),
1121 new Locale("en", "US"),
1122 new Locale("en", "US", "Win"),
1123 new Locale("en", "US", "Win_XP"),
1124 new Locale("ja", "JP"),
1125 new Locale("ja", "JP", "JP"),
1126 new Locale("th", "TH"),
1127 new Locale("th", "TH", "TH"),
1128 new Locale("no", "NO"),
1129 new Locale("nb", "NO"),
1130 new Locale("nn", "NO"),
1131 new Locale("no", "NO", "NY"),
1132 new Locale("nn", "NO", "NY"),
1133 new Locale("he", "IL"),
1134 new Locale("he", "IL", "var"),
1135 new Locale("Language", "Country", "Variant"),
1136 new Locale("", "US"),
1137 new Locale("", "", "Java"),
1138 Locale.forLanguageTag("en-Latn-US"),
1139 Locale.forLanguageTag("zh-Hans"),
1140 Locale.forLanguageTag("zh-Hant-TW"),
1141 Locale.forLanguageTag("ja-JP-u-ca-japanese"),
1142 Locale.forLanguageTag("und-Hant"),
1143 Locale.forLanguageTag("und-a-123-456"),
1144 Locale.forLanguageTag("en-x-java"),
1145 Locale.forLanguageTag("th-TH-u-ca-buddist-nu-thai-x-lvariant-TH"),
1146 };
1147
1148 for (Locale locale : testLocales) {
1149 try {
1150
1151 ByteArrayOutputStream bos = new ByteArrayOutputStream();
1152 ObjectOutputStream oos = new ObjectOutputStream(bos);
1153 oos.writeObject(locale);
1154
1155
1156 ByteArrayInputStream bis = new ByteArrayInputStream(bos.toByteArray());
1157 ObjectInputStream ois = new ObjectInputStream(bis);
1158 Object o = ois.readObject();
1159
1160 assertEquals("roundtrip " + locale, locale, o);
1161 } catch (Exception e) {
1162 errln(locale + " encountered exception:" + e.getLocalizedMessage());
1163 }
1164 }
1165 }
1166
1167 public void testDeserialize6() {
1168 final String TESTFILEPREFIX = "java6locale_";
1169
1170 File dataDir = null;
1171 String dataDirName = System.getProperty("serialized.data.dir");
1172 if (dataDirName == null) {
1173 URL resdirUrl = getClass().getClassLoader().getResource("serialized");
1174 if (resdirUrl != null) {
1175 try {
1176 dataDir = new File(resdirUrl.toURI());
1177 } catch (URISyntaxException urie) {
1178 }
1179 }
1180 } else {
1181 dataDir = new File(dataDirName);
1182 }
1183
1184 if (dataDir == null || !dataDir.isDirectory()) {
1185 errln("Could not locate the serialized test case data location");
1186 return;
1187 }
1188
1189 File[] files = dataDir.listFiles();
1190 for (File testfile : files) {
1191 if (testfile.isDirectory()) {
1192 continue;
1193 }
1194 String name = testfile.getName();
1195 if (!name.startsWith(TESTFILEPREFIX)) {
1196 continue;
1197 }
1198 Locale locale;
1199 String locStr = name.substring(TESTFILEPREFIX.length());
1200 if (locStr.equals("ROOT")) {
1201 locale = Locale.ROOT;
1202 } else {
1203 String[] fields = locStr.split("_", 3);
1204 String lang = fields[0];
1205 String country = (fields.length >= 2) ? fields[1] : "";
1206 String variant = (fields.length == 3) ? fields[2] : "";
1207 locale = new Locale(lang, country, variant);
1208 }
1209
1210
1211 try (FileInputStream fis = new FileInputStream(testfile);
1212 ObjectInputStream ois = new ObjectInputStream(fis))
1213 {
1214 Object o = ois.readObject();
1215 assertEquals("Deserialize Java 6 Locale " + locale, o, locale);
1216 } catch (Exception e) {
1217 errln("Exception while reading " + testfile.getAbsolutePath() + " - " + e.getMessage());
1218 }
1219 }
1220 }
1221
1222 public void testBug7002320() {
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233 String[][] testdata = {
1234 {"ja-JP-x-lvariant-JP", "ja-JP-u-ca-japanese-x-lvariant-JP"},
1235 {"ja-JP-x-lvariant-JP-XXX"},
1236 {"ja-JP-u-ca-japanese-x-lvariant-JP"},
1237 {"ja-JP-u-ca-gregory-x-lvariant-JP"},
1238 {"ja-JP-u-cu-jpy-x-lvariant-JP"},
1239 {"ja-x-lvariant-JP"},
1240 {"th-TH-x-lvariant-TH", "th-TH-u-nu-thai-x-lvariant-TH"},
1241 {"th-TH-u-nu-thai-x-lvariant-TH"},
1242 {"en-US-x-lvariant-JP"},
1243 };
1244
1245 Builder bldr = new Builder();
1246
1247 for (String[] data : testdata) {
1248 String in = data[0];
1249 String expected = (data.length == 1) ? data[0] : data[1];
1250
1251
1252 Locale loc = Locale.forLanguageTag(in);
1253 String out = loc.toLanguageTag();
1254 assertEquals("Language tag roundtrip by forLanguageTag with input: " + in, expected, out);
1255
1256
1257 bldr.clear();
1258 bldr.setLanguageTag(in);
1259 loc = bldr.build();
1260 out = loc.toLanguageTag();
1261 assertEquals("Language tag roundtrip by Builder.setLanguageTag with input: " + in, expected, out);
1262 }
1263 }
1264
1265 public void testBug7023613() {
1266 String[][] testdata = {
1267 {"en-Latn", "en__#Latn"},
1268 {"en-u-ca-japanese", "en__#u-ca-japanese"},
1269 };
1270
1271 for (String[] data : testdata) {
1272 String in = data[0];
1273 String expected = (data.length == 1) ? data[0] : data[1];
1274
1275 Locale loc = Locale.forLanguageTag(in);
1276 String out = loc.toString();
1277 assertEquals("Empty country field with non-empty script/extension with input: " + in, expected, out);
1278 }
1279 }
1280
1281
1282
1283
1284 public void testBug7033504() {
1285 checkCalendar(new Locale("ja", "JP", "jp"), "java.util.GregorianCalendar");
1286 checkCalendar(new Locale("ja", "jp", "jp"), "java.util.GregorianCalendar");
1287 checkCalendar(new Locale("ja", "JP", "JP"), "java.util.JapaneseImperialCalendar");
1288 checkCalendar(new Locale("ja", "jp", "JP"), "java.util.JapaneseImperialCalendar");
1289 checkCalendar(Locale.forLanguageTag("en-u-ca-japanese"),
1290 "java.util.JapaneseImperialCalendar");
1291
1292 checkDigit(new Locale("th", "TH", "th"), '0');
1293 checkDigit(new Locale("th", "th", "th"), '0');
1294 checkDigit(new Locale("th", "TH", "TH"), '\u0e50');
1295 checkDigit(new Locale("th", "TH", "TH"), '\u0e50');
1296 checkDigit(Locale.forLanguageTag("en-u-nu-thai"), '\u0e50');
1297 }
1298
1299 private void checkCalendar(Locale loc, String expected) {
1300 Calendar cal = Calendar.getInstance(loc);
1301 assertEquals("Wrong calendar", expected, cal.getClass().getName());
1302 }
1303
1304 private void checkDigit(Locale loc, Character expected) {
1305 DecimalFormatSymbols dfs = DecimalFormatSymbols.getInstance(loc);
1306 Character zero = dfs.getZeroDigit();
1307 assertEquals("Wrong digit zero char", expected, zero);
1308 }
1309
1310
1311
1312
1313
1314 private void assertTrue(String msg, boolean v) {
1315 if (!v) {
1316 errln(msg + ": expected true");
1317 }
1318 }
1319
1320 private void assertFalse(String msg, boolean v) {
1321 if (v) {
1322 errln(msg + ": expected false");
1323 }
1324 }
1325
1326 private void assertEquals(String msg, Object e, Object v) {
1327 if (e == null ? v != null : !e.equals(v)) {
1328 if (e != null) {
1329 e = "'" + e + "'";
1330 }
1331 if (v != null) {
1332 v = "'" + v + "'";
1333 }
1334 errln(msg + ": expected " + e + " but got " + v);
1335 }
1336 }
1337
1338 private void assertNotEquals(String msg, Object e, Object v) {
1339 if (e == null ? v == null : e.equals(v)) {
1340 if (e != null) {
1341 e = "'" + e + "'";
1342 }
1343 errln(msg + ": expected not equal " + e);
1344 }
1345 }
1346
1347 private void assertNull(String msg, Object o) {
1348 if (o != null) {
1349 errln(msg + ": expected null but got '" + o + "'");
1350 }
1351 }
1352
1353 private void assertNotNull(String msg, Object o) {
1354 if (o == null) {
1355 errln(msg + ": expected non null");
1356 }
1357 }
1358
1359
1360 private abstract class ExceptionTest {
1361 private final Class<? extends Exception> exceptionClass;
1362
1363 ExceptionTest(Class<? extends Exception> exceptionClass) {
1364 this.exceptionClass = exceptionClass;
1365 }
1366
1367 public void run() {
1368 String failMsg = null;
1369 try {
1370 call();
1371 failMsg = "expected " + exceptionClass.getName() + " but no exception thrown.";
1372 }
1373 catch (Exception e) {
1374 if (!exceptionClass.isAssignableFrom(e.getClass())) {
1375 failMsg = "expected " + exceptionClass.getName() + " but caught " + e;
1376 }
1377 }
1378 if (failMsg != null) {
1379 String msg = message();
1380 msg = msg == null ? "" : msg + " ";
1381 errln(msg + failMsg);
1382 }
1383 }
1384
1385 public String message() {
1386 return null;
1387 }
1388
1389 public abstract void call();
1390 }
1391
1392 private abstract class ExpectNPE extends ExceptionTest {
1393 ExpectNPE() {
1394 super(NullPointerException.class);
1395 run();
1396 }
1397 }
1398
1399 private abstract class BuilderNPE extends ExceptionTest {
1400 protected final String msg;
1401 protected final Builder b = new Builder();
1402
1403 BuilderNPE(String msg) {
1404 super(NullPointerException.class);
1405
1406 this.msg = msg;
1407
1408 run();
1409 }
1410
1411 public String message() {
1412 return msg;
1413 }
1414 }
1415
1416 private abstract class ExpectIAE extends ExceptionTest {
1417 ExpectIAE() {
1418 super(IllegalArgumentException.class);
1419 run();
1420 }
1421 }
1422
1423 private abstract class BuilderILE extends ExceptionTest {
1424 protected final String[] args;
1425 protected final Builder b = new Builder();
1426
1427 protected String arg;
1428
1429 BuilderILE(String... args) {
1430 super(IllformedLocaleException.class);
1431
1432 this.args = args;
1433
1434 run();
1435 }
1436
1437 public void run() {
1438 for (String arg : args) {
1439 this.arg = arg;
1440 super.run();
1441 }
1442 }
1443
1444 public String message() {
1445 return "arg: '" + arg + "'";
1446 }
1447 }
1448 }